Warp Six BBS Documentation Updated September 4, 1989 Copyright 1989 Jim Ferr All rights reserved. Table of Contents 1) File Specifications 2) Machine Language Routines Specifications 3) Making customizations to the drivers 4) Programming Considerations Getting Input Output Summary Notes Appendix A: Local Commands 1) File Specifications (ROOT DIRECTORY) STARTUP - a BASIC program that executes the Warp6.Loader and runs LOGON. WARP6.LOADER - loads the driver, allocates interrupt handler, sets vectors and turns on the 80 column card if one is present. WARP6.DRIVER - the input/output driver, called from BASIC. MODEM.INIT - a one or more line text file to initialize the modem LOGON - a BASIC program that sets up all variables, waits for calls and handles logon procedures. WARP6.BBS - the BBS itself, including main command level, forums and E-mail. SYSOP.UTIL - sysop utilities ADD.A.FORUM - CHAINed from Sysop.Utilities USER.PURGE - CHAINed from Warp6.BBS ADD.USER - CHAINed from LOGON to sign up new users FILER - CHAINed from Warp6.BBS to handle file sections UPLOADER - CHAINed from Warp6.BBS to handle text uploads AWORKS.CONVERT - a stand-alone utility to convert the USERS file to a standard text file that AppleWorks can read. (17 fields per record) BKUP.STARTUP - a BASIC program you should install on a ProDOS boot disk on your the floppy disk your system will boot from in case of power failure. SET.TO.40COL - a text file you can EXEC to modify LOGON for 40 column display if you don't have an 80 column card installed. UCASE - A UTILITY TO CONVERT APPLESOFT PROGRAMS TO ALL UPPERCASE UCASE.DOC - DOCS FOR ABOVE Other important files: Bytes per field in parentheses () USERS, type TXT Record Length=135 ID/UI User ID number. Always R+1000. (5) PW$/UP$ Password (8) N1$/N3$ First Name (16) N2$/N4$ Last Name (21) A1$/A3$ City (20) A2$/A4$ Province/State/Country (3) PH$/TE$ Phone number, nnn-nnn-nnnn (13) DV$/VD$ Date Validated (10) LD$/DL$ Date Last on (10) LT$/TL$ Time last on (5) TD/DT calls today (2) SL/US Security Level (0-9) defined: (2) 0 = unvalidated/guest 1 = devalidated 2 = validated user 3 = regular contributor 4-9 = future use MT/UT Machine Type. defined: (2) 0 = undefined 1 = Apple // or compatible 2 = Macintosh, Mac XL or Mac Plus 3 = IBM or compatible 4 = Other BP/UP Bulletins posted (5) ME/MB Membership flag, 0=off, 1=on (2) TM/UM Total Mail waiting (3) TC/TK Total Calls made (5) Per Record Total: 17 fields, 132 bytes, 2 spare, 1 for EOR. REC.DATA, type TXT LR Last Record used in USERS file RN Reference number of last bulletin posted in system (10000-99999) SYS.DATA, type TXT RT$ Root Pathname for system FP$ Forum dir pathname EP$ Email dir pathname SN$ System Name SP$ Copyright message or system sponsor RP$ Remote (Sysop) Password HR$ Hours/baud rate message AB$ abort string (Control-S to pause...) CS Clock slot FC Forum Count: total # of forums CD$ Current date in ProDOS format CT Call Total for System MODEM.INIT Holds initialization strings for the modem. Two is the maximum recommended. See Modem.Doc for details. LOG N1$+" "+N2$ User first and last name LOG.REC Y Holds total number of users in LOG. ERROR.LOG Log of errors in operation UNVALIDATED TYPED to unvalidated callers DEVALIDATED TYPED to devalidated callers NEW.INFO Info message to NEW callers DUPLICATE TYPED if new user enters duplicate name REJECT.USER Used in the event of an error in Add.User AGREEMENT TYPED to all new users BAD.ID TYPED if bad ID number entered twice SYS.NEWS TYPED to all callers at logon. MAIN.MENU Main Menu, TYPED at '?' command SYS.MENU Sysop Menu, TYPED after MAIN.MENU SYSTEM.MENU Sysop.Util menu FORUM.NAMES TYPED menu (numbered) of forum names FORUM.HELP TYPED list of Forum Commands EDIT.HELP TYPED list of Edit Commands READ.HELP TYPED when caller hits ? at read prompt ABOUT.US About your BBS. From main menu. (FORUM DIRECTORIES) OPENER This file is TYPED upon entry into a forum F.DATA FM$ Forum name ES Entry security (min.) 0-9 WS Write security (min.) 0-9 MO Members only flag (0-1) BL Bulletin limit FD First bulletin to delete at limit TT Total Titles in forum LB refnum of last msg. posted in this forum U.DATA TXT L=6 RL last bulletin read by each user, indexed by record number where R=ID-1000 GEN DIRECTORY F.DATA Holds name of file section and number of sub-sections TITLES Menu of sub-sections Fn Subdirectories F1 to Fwhatever hold actual general files GEN/Fn DIRECTORIES F.DATA Holds name of section and number of files TITLES Holds menu of files Fn Files F1 to Fwhatever are the files themselves. TITLES TI$(X) where X is TT Titles are in the following format: "B"+"."+STR$(ID)+"."+STR$(RN)+MID$(SU$,8) Eg. B.1000.15844This is the title BULLETINS Bulletins are stored as text and TYPED. Example of bulletin filename: B.1000.10437 The first few fields compose the bulletin header. The FROM field is INPUT into memory for the Post reply feature. EMAIL Similar to bulletins, but filenames are M.1000.1 where 1000 is the ID number and 1 is the letter number. 2) Warp6 Machine Language Routines Specifications WARP6.DRIVER contains the following routines: M/L NAME BASIC NAME FUNCTION INIT M1 Sets up all M/L flags and variables. GETCALL M2 Waits for call or local command. GETLN M3 This is the line input routine. LOGON M4 Called at connect to save starting time. GETTIME M5 Updates ProDOS date and time if clock. HANGUP M6 Drops DTR to hangup, and disables interrupts. CLRMBUF M7 Clears the modem buffer of data. INIT2 M0 Set up modem by sending MODEM.INIT file to modem All the above routines are vectored, so their locations will not change with minor revisions to the driver programs. To activate a routine, just CALL it, for example CALL M6 to hangup. Note that the user's elapsed time is continually updated (each time the user presses RETURN, actually). (The locations of these routines are defined in LOGON near the beginning.) 3) Making Customizations to the live drivers There are a few things you can do to change the live drivers. If your cpu is faster than the standard 1Mhz Apple IIe or IIc, you should change the timeout values using POKEs. You can put these at the beginning of the LOGON program (before line 100), or you can patch the driver of your choice permanently. Here are the timeout counters you can change, and their locations: Name Hex Decimal Default Description (decimal) TMOUT $8F2F 36665 21 Defines how long to wait for input before sending warning and hanging up. Default is about 3 minutes. OTMOUT $8F33 36659 38 Defines how long to wait for Xon after user pressed Control-S to pause. Default is about 3 minutes. OKCHECK $8F37 36663 7 Defines how often the driver checks the modem. Default about every 30 secs. INTMOUT $8F38 36664 6 Defines the initial timeout when a caller first logs on. About 30 secs. DEFBAUD $8F3C 36668 3 1=300, 2=1200, 3=2400 DELAY1B $8F3D 36669 5 Counter to pause 1 sec on 1Mhz system To change a timeout value, use the POKE statement (POKE LOCATION,VALUE), for example POKE 36659,55. The values must be within 1 and 255 to be valid. Be careful when changing these values. With version 3.03, the BASE address (address of M1) is predefined in LOGON as BA. To change the default baud rate to 1200 baud, use POKE BA+49,2. DEFBAUD is at BASE + 49, or 36619 + 49 = 36668. The same method can be applied to any values above. The advantage to you is that if another driver is released, you just change the value of BA, not POKEs located all over the program. To make a permanent change, exit to BASIC from the BBS using the + command at the main menu. (Changes will affect your live driver.) Then do a ProDOS disk CATALOG and take note of the length of the driver you are using. Use CALL-151 to get into the monitor and type 8F37: 1F and press Return (for example) to change a value. To get back into BASIC to save, use Control-C Return. Then use BSAVE WARP6.DRIVER,A$8F00,Lnnnn where L is the decimal length you took note of in the catalog earlier. There are a few other changes you can make, if you are ambitious. All text strings are terminated with a hex zero. If you change a string, you must leave it the same size and leave the zero byte intact. (Program execution continues after the hex zero byte.) Further changes than this are not recommended. If you make a change to a string and decrease its size, you must put in spaces before the 0 byte, or NOP's after it. A No-Op is a hexidecimal EA. 4) Programming Considerations If you are a glutton for punishment, you can make modifications to the system. Just keep in mind the following caveats. Have a backup copy of the original unmodified program in a safe place. Make another backup of the program on another disk before every change you make. Test all changes thoroughly for unexpected bugs before subjecting them to your users. To make a major addition you should write additional programs which can either be run or CHAINed from the main program. A good example of this technique is the SYSOP.UTIL program. There is more information on common modifications in the Sysop.Doc file. And now for some details. Getting Input Before getting input, do the following: POKE VI,x, where x is the maximum length of characters you want to accept. A value of zero will only accept a carriage return. The video width is preset to 80 columns - 2, and is stored in VW. POKE UC,0 to enable full upper and lower case. POKE UC,255 to convert characters in range a-z to uppercase. POKE MD,255 to echo asterisks when taking input. (This is the hidden mode, and is generally used to take password input. Hidden mode is automatically shut off when the user presses RETURN. CALL M7 to clear the modem buffer if you wish. Most times this is not desirable. PRINT a prompt, for example PRINT:PRINT"Enter your name : "; (Note the semicolon. It is necessary to suppress the carriage return in your prompt.) Note that the options above (except for the MODE flag) will remain as you last set them, so it is not always necessary to do each poke. After setting the above options, do a GOSUB 100 to get a line of input with time limit active. If the user is out of time, he will be logged off. If he has five minutes or less time remaining, and he hasn't already been warned, he will be. Do GOSUB 130 to get a line of input with time limit ignored. When control returns, the input will be in I$. If CR=1 then the user pressed RETURN. Do a GOSUB 170 to check for commas, colons or dashes. Then if EE=1 the user did enter one of these, so do a GOSUB 190 to reject the input, and then GOTO the line requesting the input again. It is possible control will not return after a GOSUB 100 or 130 to get input, if the caller drops carrier (ie. hangs up) or a control-K (kill command) is issued from the console. The input routine will automatically branch to the logoff code if this happens. The system is designed to fully recover after any premature disconnection, and will fully save the users stats before getting another call. Output As already mentioned, you can simply use PRINT statements to send output. In addition, there is the built-in TYPE command, which will read standard ASCII text files (with high bit set or clear) to the current output. Eg. PRINT D$"TYPE MY.FILE" will dump the contents of MY.FILE, regardless of its contents. IMPORTANT NOTE: DO NOT USE ANY PR# COMMANDS AS YOU WILL DISCONNECT THE OUTPUT ROUTINE THE SYSTEM USES TO SEND DATA TO THE MODEM. You should never ever use in# and input to get user input. Use gosub 100 or 130 exclusively. Getting input via in# and 'input' would leave your system wide open to hackers in the unlikely event of a crash. The machine language input routines must be called to get input. This provides the ultimate in security for your system: in the event the system crashes, the remote user can't input anything. There is only one output option: the private flag. If you do a POKE PF,255 before sending output, the output will only go to the modem (if active). A POKE PF,0 reverses this condition. The system uses the private flag to ensure E-mail is not displayed on the console screen. Thus you as sysop cannot read user mail unless you read it directly from disk, which is considered to be in extremely poor taste unless you display a prominent message telling users you will be scanning mail. Note that mail directed to the sysop WILL be displayed. Summary The program is written in a modular fashion, as a cursory glance at the program description will tell you. If you have questions, give me a call. If you decide to make a major improvement to your system, let me know so I can help. I would appreciate it if you can "donate" any major enhancements. Many people have helped along the evolution of the current system. Many improvements have been made to the system, some of which may not have made it into this documentation. Notes To halt program execution hit Control-Reset. Control-C will merely cause an error #255, which will be trapped and logged by the system. Because the system uses interrupts for modem input, an interrupt handler is allocated. Use the Quit command (control-Q) to properly deallocate the interrupt handler and disable interrupts from the SSC. Read your error log frequently. You shouldn't experience many errors in normal operation. APPENDIX A: Local commands Active while awaiting a call: Control-L :local logon/logoff toggle (hitting Ctrl-L while online is like dropping carrier. Control-Q :quit program (disables interrupts, and removes handler) Active while user online: Control-A :activate/deactivate local keyboard for input (Used to enter information for an online user, eg. to give a guided tour.) Control-O :sysop online/offline toggle for chat Control-P :promote user one security level Control-D :demote user one security level Control-K :kill call (hangup on remote caller.) Displays "Killed." Control-W :warning - "1 minute left!"